#pragma once

#include "Ex.h"

#include <gtl/vec3.hpp>

namespace Math
{
    /**
    * Describes a so-called tube. Bases of a tube are ellipses. The focal radius of the bases are 
    * equal. Electromagnetic field between two wires can be represented as a tube. 
    */
    class Tube : public IGeometry
    {
    public:
        /**
        * \param pp1 focuses of the first base 
        * \param pp2 focuses of the second base
        * \param width width of the tube
        * \param height height of the tube that is appropriate to the width 
        */
        Tube(const std::pair<gtl::Vec3d, gtl::Vec3d> & pp1
            , const std::pair<gtl::Vec3d, gtl::Vec3d> & pp2, double width, double height);
        
        /**
        * \param pp1 focuses of the first base 
        * \param pp2 focuses of the second base
        * \param fradius focal radius of the bases
        */
        Tube(const std::pair<gtl::Vec3d, gtl::Vec3d> & pp1
            , const std::pair<gtl::Vec3d, gtl::Vec3d> & pp2, double fradius);
        
        bool Inside(const gtl::Vec3d & pt) const;

        /**
        * Local coordinates equal to global ones. The mothod does nothing
        */
        virtual gtl::Vec3d ConvertToGlobal(const gtl::Vec3d & localPos) const;
        
        /**
        * Global coordinates equal to local ones. The mothod does nothing
        */
        virtual gtl::Vec3d ConvertToLocal(const gtl::Vec3d & globalPos) const;
        
    private:
        void Init(const std::pair<gtl::Vec3d, gtl::Vec3d> & pp1
            , const std::pair<gtl::Vec3d, gtl::Vec3d> & pp2, double focalRadius);

    private:
        gtl::Vec3d p11;
        gtl::Vec3d p12;
        gtl::Vec3d p21;
        gtl::Vec3d p22;
        double fradius;

        gtl::Planed plane1;
        gtl::Planed plane2;
        gtl::Vec3d center1;
        gtl::Vec3d center2;
    };
}
